package cn.npe.dynamic.thread.pool.sdk.trigger.job;

import cn.npe.dynamic.thread.pool.sdk.domain.IDynamicThreadPoolService;
import cn.npe.dynamic.thread.pool.sdk.domain.model.entity.ThreadPoolConfigEntity;
import cn.npe.dynamic.thread.pool.sdk.registry.DtpContext;
import cn.npe.dynamic.thread.pool.sdk.registry.IRegistry;
import com.alibaba.fastjson.JSON;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang.StringUtils;
import org.springframework.beans.BeansException;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
import org.springframework.context.SmartLifecycle;

import java.util.List;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledFuture;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;

@Slf4j
public class DtpMonitor implements SmartLifecycle, ApplicationContextAware {

    private ScheduledFuture<?> scheduledFuture;

    private boolean isRunning=false;

    private IDynamicThreadPoolService dynamicThreadPoolService;
    private IRegistry registry;
    private boolean isRegistryEnabled=false;

    private void monitor() {
        for (String name :  DtpContext.getAllExecutorNames()) {
            ThreadPoolExecutor dtpExecutor =(ThreadPoolExecutor) DtpContext.getExecutor(name);
            System.out.println(String.format("线程池名字：%s", name));
            System.out.println(String.format("线程池核心线程数：%s", dtpExecutor.getCorePoolSize()));
            System.out.println(String.format("线程池最大线程数：%s", dtpExecutor.getMaximumPoolSize()));
            System.out.println(String.format("线程池当前线程数：%s", dtpExecutor.getActiveCount()));
            System.out.println(String.format("线程池当前剩余队列数：%s", dtpExecutor.getQueue().remainingCapacity()));
        }
    }

    private void alarm() {
        // 读取配置
        int max = 10;
        for (ThreadPoolExecutor threadPoolExecutor : DtpContext.getAllDtpExecutor()) {
            int activeCount = threadPoolExecutor.getActiveCount();
            if (activeCount >= max) {
                System.out.println(String.format("告警，当前线程池的线程个数为%s, 告警阈值为%s", activeCount, max));
            }
        }
    }
    /**
     * @return
     * @date
     * @description  上报数据
     */
    private void reportThreadPoolInfo(){
        List<ThreadPoolConfigEntity> threadPoolConfigEntities = dynamicThreadPoolService.queryThreadPoolList();
        registry.reportThreadPool(threadPoolConfigEntities);
        log.info("动态线程池，上报线程池信息：{}", JSON.toJSONString(threadPoolConfigEntities));
        for (ThreadPoolConfigEntity threadPoolConfigEntity : threadPoolConfigEntities) {
            registry.reportThreadPoolConfigParameter(threadPoolConfigEntity);
            log.info("动态线程池，上报线程池配置：{}", JSON.toJSONString(threadPoolConfigEntity));
        }
    }

    @Override
    public void start() {
         scheduledFuture = Executors.newSingleThreadScheduledExecutor().scheduleAtFixedRate(() -> {
//            monitor();
//            alarm();
            if(this.isRegistryEnabled){
                reportThreadPoolInfo();
            }
        }, 5, 20, TimeUnit.SECONDS);
        isRunning=true;
    }

    @Override
    public void stop() {
        scheduledFuture.cancel(false);
        isRunning=false;
    }

    @Override
    public boolean isRunning() {
        return isRunning;
    }

    @Override
    public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
        this.dynamicThreadPoolService=applicationContext.getBean(IDynamicThreadPoolService.class);
        String flag=applicationContext.getEnvironment().getProperty("spring.dtp.registry.enabled");
        this.isRegistryEnabled= StringUtils.isNotEmpty(flag)&&"true".equals(flag);
        if(this.isRegistryEnabled) {
            this.registry = applicationContext.getBean(IRegistry.class);
        }
    }
}